package com.demo.accessibility.widgets

/// @Author: ligang
/// @Date: 2024/6/2
/// @Description:
import android.content.Context
import android.graphics.Canvas
import android.graphics.drawable.Drawable
import android.text.TextPaint
import android.util.AttributeSet
import androidx.appcompat.widget.AppCompatTextView
import com.demo.accessibility.R

class IconLabelTextView @JvmOverloads constructor(
    context: Context,
    attrs: AttributeSet? = null,
    defStyleAttr: Int = 0
) : AppCompatTextView(context, attrs, defStyleAttr) {

    private var icon: Drawable? = null
    private var iconPaddingStart: Int = 0
    private var iconPaddingTop: Int = 0
    private var iconPaddingBottom: Int = 0

    private var mIconWidth = 0
    private var mIconHeight = 0

    var mCallback: ((left: Int, top: Int, right: Int, bottom: Int) -> Unit)? = null

    init {
        attrs?.let {
            val a = context.obtainStyledAttributes(it, R.styleable.IconLabelTextView)
            icon = a.getDrawable(R.styleable.IconLabelTextView_iconSrc)
            iconPaddingStart =
                a.getDimensionPixelSize(R.styleable.IconLabelTextView_iconPaddingStart, 0)
            iconPaddingTop =
                a.getDimensionPixelSize(R.styleable.IconLabelTextView_iconPaddingTop, 0)
            iconPaddingBottom =
                a.getDimensionPixelSize(R.styleable.IconLabelTextView_iconPaddingBottom, 0)
            a.recycle()
        }
    }

    override fun onDraw(canvas: Canvas?) {
        super.onDraw(canvas)
        canvas?.let {
            val textPaint: TextPaint = paint
            val lineHeight = textPaint.descent() - textPaint.ascent()
            val lineSpacingExtra = lineSpacingExtra // 获取行间距
            val layout = layout ?: return

            for (i in 0 until layout.lineCount) {
                val lineStart = layout.getLineStart(i)
                val lineEnd = layout.getLineEnd(i)
                val lineText = text.subSequence(lineStart, lineEnd).toString()
                val textWidth = textPaint.measureText(lineText)
                val availableWidth = width - paddingLeft - paddingRight
                val iconWidth = if (mIconWidth != 0) mIconWidth else icon?.intrinsicWidth ?: 0
                val iconHeight = if (mIconHeight != 0) mIconHeight else icon?.intrinsicHeight ?: 0

                if (i == layout.lineCount - 1) {
                    // 如果文本加上图标宽度超过可用宽度，将图标换行显示
                    if (textWidth + iconWidth + iconPaddingStart > availableWidth) {
                        val newLineY =
                            paddingTop + lineHeight * (i + 1) + lineSpacingExtra * (i + 1)
                        val iconX = paddingLeft + iconPaddingStart
                        icon?.setBounds(
                            iconX,
                            newLineY.toInt(),
                            iconX + iconWidth,
                            newLineY.toInt() + iconHeight
                        )
                        text = "$text\n"
                        icon?.draw(it)
                        mCallback?.invoke(
                            iconX,
                            newLineY.toInt(),
                            iconX + iconWidth,
                            newLineY.toInt() + iconHeight
                        )
                    } else {
                        // 文本和图标在同一行
                        val iconY =
                            paddingTop + lineHeight * i + (lineHeight - iconHeight) / 2 + iconPaddingTop - iconPaddingBottom + lineSpacingExtra * i
                        val iconX = paddingLeft + textWidth + iconPaddingStart
                        icon?.setBounds(
                            iconX.toInt(),
                            iconY.toInt(),
                            (iconX + iconWidth).toInt(),
                            (iconY + iconHeight).toInt()
                        )
                        icon?.draw(it)
                        mCallback?.invoke(
                            iconX.toInt(),
                            iconY.toInt(),
                            (iconX + iconWidth).toInt(),
                            (iconY + iconHeight).toInt()
                        )
                    }
                }
            }
        }
    }

    fun setIcon(
        icon: Drawable?,
        paddingStart: Int,
        paddingTop: Int,
        paddingBottom: Int,
        iconWidth: Int = 0,
        iconHeight: Int = 0
    ) {
        this.icon = icon
        this.iconPaddingStart = paddingStart
        this.iconPaddingTop = paddingTop
        this.iconPaddingBottom = paddingBottom
        mIconWidth = iconWidth
        mIconHeight = iconHeight
        invalidate()
    }
}


